#include "Camera.h"


CCamera::CCamera(void)
{
}


CCamera::~CCamera(void)
{
}

void CCamera::Init()
{
	
	m_alpha = m_beta = XM_PI / 6.0f;
	m_radius = 10.0f;
	m_fov = XM_PI / 4.0f;

	m_eye = vec3 (50.0f, 50.0f, 50.0f);
	m_focus = vec3 (0.0f, 0.0f, 0.0f);
}

void CCamera::Scroll(vec3 vec)
{
	vec3 newFocus = m_focus + vec;

	if(newFocus.x > -50.0f && newFocus.x < 50.0f &&
		newFocus.z > -50.0f && newFocus.z < 50.0f)
		m_focus = newFocus;
}

void CCamera::Pitch(float f)
{
	m_beta += f;

	if(m_beta > XM_PI / 2.0f) m_beta = XM_PI / 2.0f - 0.01f;
	if(m_beta < 0.3f) m_beta = 0.3f;
}

void CCamera::Yaw(float f)
{
	m_alpha += f;
	if(m_alpha > XM_PI * 2.0f)m_alpha -= XM_PI * 2.0f;
	if(m_alpha < -XM_PI * 2.0f)m_alpha += XM_PI * 2.0f;
}

void CCamera::Zoom(float f)
{
	m_fov += f;

	if(m_fov < 0.1f)m_fov = 0.1f;
	if(m_fov > XM_PI / 2.0f)m_fov = XM_PI / 2.0f;
}

void CCamera::ChangeRadius(float f)
{
	m_radius += f;

	if(m_radius < 5.0f)m_radius = 5.0f;
	if(m_radius > 400.0f)m_radius = 400.0f;
}

void CCamera::Update(float timeDelta)
{
	//Restrict focus movment to the xz-plane
	m_right.y = m_look.y = 0.0f;
	m_look.Normalize();
	m_right.Normalize();

	//Move Focus (i.e. Scroll)
	if(KEYDOWN(VK_LEFT))Scroll(-m_right * timeDelta * 20.0f);
	if(KEYDOWN(VK_RIGHT))Scroll(m_right * timeDelta * 20.0f);
	if(KEYDOWN(VK_UP))Scroll(m_look * timeDelta * 20.0f);
	if(KEYDOWN(VK_DOWN))Scroll(-m_look * timeDelta * 20.0f);

	//Move CCamera (i.e. Change Angle)
	if(KEYDOWN('A'))Yaw(-timeDelta);
	if(KEYDOWN('D'))Yaw(timeDelta);
	if(KEYDOWN('W'))Pitch(timeDelta);
	if(KEYDOWN('S'))Pitch(-timeDelta);

	if(KEYDOWN(VK_SHIFT))
	{
		//Zoom (i.e. change m_fov)
		if(KEYDOWN(VK_ADD))Zoom(-1.0f * timeDelta);
		if(KEYDOWN(VK_SUBTRACT))Zoom(timeDelta);
	}
	else
	{
		//Change m_radius
		if(KEYDOWN(VK_ADD))ChangeRadius(-1.0f * timeDelta * 100.0f);
		if(KEYDOWN(VK_SUBTRACT))ChangeRadius(timeDelta * 100.0f);
	}

	//Calculate Eye Position
	float sideRadius = m_radius * cos(m_beta);
	float height = m_radius * sin(m_beta);

	m_eye = vec3(m_focus.x + sideRadius * cos(m_alpha),
		m_focus.y + height, 
		m_focus.z + sideRadius * sin(m_alpha));

}

mat4 CCamera::GetViewMatrix()
{
	mat4  matView = MatrixLookAt(m_eye, m_focus, vec3(0.0f, 1.0f, 0.0f));

	m_right.x = matView(0,0);
	m_right.y = matView(0,1);
	m_right.z = matView(0,2);
	m_right.Normalize();

	m_look.x = matView(2,0);
	m_look.y = matView(2,1);
	m_look.z = matView(2,2);
	m_look.Normalize();

	return  matView;
}

mat4 CCamera::GetProjectionMatrix()
{
	mat4  matProj = MatrixPerspectiveFOV(m_fov, 640.0f, 480.0f, 1.0f, 1000.0f );
	return matProj;
}
